#!/usr/bin/env python
#
# Component that implements subscription update/checking logic
#
# Name: F.U.N.S.
# Author: Douglas Turner
# Revision: 12 January 2013
#
#   Copyright 2013 Coastal Carolina University
#
#   Licensed under the Apache License, Version 2.0 (the "License");
#   you may not use this file except in compliance with the License.
#   You may obtain a copy of the License at
#
#       http://www.apache.org/licenses/LICENSE-2.0
#
#   Unless required by applicable law or agreed to in writing, software
#   distributed under the License is distributed on an "AS IS" BASIS,
#   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
#   See the License for the specific language governing permissions and
#   limitations under the License
#
#
#

import grp
import os
import pwd
import pynotify
import resource
import subprocess
import sys
import time
import wx


def check_updates(self, temp, notification):
	updates= 0	
	try:
		updates= subprocess.call(["pulley", "check-update"])
	except Exception:
		updates= 0
	#
	if updates == 100:
		temp.update_tb()
		notification.goNotify()
	# 
	self.timer()
#

#Creates a notification bubble that lasts for 10 seconds when goNotify is called
class UpdateNotification():
	def __init__(self):
		pynotify.init("Update Notification")
		self.d = pynotify.Notification("Updates Available.", "Click the icon in the taskbar.")
		self.d.set_category("Updates")
		self.d.set_timeout(10000)
	#
	def goNotify(self):
		self.d.show()
	#
#

#Cancel button event handler
def window_cancel(self, windowTemp): 
	windowTemp.Hide()
#

#Continue button event handler
#Stops the timer and creates a one shot timer for 1 second to allow updates to 
#begin using a flag in TimeChecker.Notify()
def window_continue(self, windowTemp, timer, tb_temp):
	windowTemp.Hide()
	tb_temp.updating_tb()
	timer.Start(1, wx.TIMER_ONE_SHOT)
	timer.updating()
#

#Creates the updates window and all of its components
class UpdatePopUp(wx.Window):
	def __init__(self, stop_handler, go_handler, timer, tb_temp, notify_temp):
		self.stop_handler= stop_handler
		self.go_handler= go_handler
		self.timer= timer
		self.tb_temp= tb_temp
		self.notify_temp= notify_temp
		self.window= wx.Frame(None, title= "Updater")
		self.text1= "Updates have been found for your computer.\nWould you like to download updates now?\n\nIt would be advisable to make sure that the current \ninternet connection is reliable and fast enough to\nperform the updates before continuing."
		self.mainText= wx.StaticText(self.window, -1, self.text1, (20, 15))
		self.continButton= wx.Button(self.window, 1, "Continue", (30, 130))
		self.continButton.Bind(wx.EVT_BUTTON, self.goClick)
		self.cancelButton= wx.Button(self.window, 1, "Cancel", (230,130))
		self.cancelButton.Bind(wx.EVT_BUTTON, self.stopClick)
		self.wsize= self.window.GetEffectiveMinSize()
		self.window.SetSize(self.wsize)	
	#
	#Cancel button
	def stopClick(self, unknown):
		self.stop_handler(unknown, self.window)
	#
	#Continue button
	def goClick(self, unknown):
		self.go_handler(self, self.window, self.timer, self.tb_temp)
	#
	#Called to show the window
	def popup_menu(self):
		self.window.Show()
	#
#

#Event handler for a click on the update_tb icon
#Shows the the window made in UpdatePopUp
def update_click(event, self):
	self.popup_menu()
#

#Creates the taskbar icons and handles all of there events
class TBIconMaker(wx.TaskBarIcon):
	def __init__(self, update, temp_notify, icon2Location, icon3Location,  timer):
		self.update= update
		self.temp_notify= temp_notify
		self.timer= timer
				
		#Initializes the window so it can be called later
		self.windowTemp= UpdatePopUp(window_cancel, window_continue, self.timer, self, self.temp_notify)
				
		#Icon image for update_tb
		self.icon2= wx.Icon(icon2Location, wx.BITMAP_TYPE_PNG)
		
		#Icon image for updating_tb
		self.icon3= wx.Icon(icon3Location, wx.BITMAP_TYPE_PNG)
		
		#Creates the icon
		self.tbIcon= wx.TaskBarIcon()
	#
	def update_tb(self):
		self.tbIcon.SetIcon(self.icon2, "Updates are available\nClick to download updates")
		self.tbIcon.Bind(wx.EVT_TASKBAR_LEFT_UP, lambda event: self.update(event, self.windowTemp))
	#
	def updating_tb(self):
		self.tbIcon.SetIcon(self.icon3, "Busy...")
	#
#
		
class UpdateChecker(wx.Timer):
	def __init__(self, interval, callback, icon2Location, icon3Location):
		wx.Timer.__init__(self)
		self.interval = interval
		self.callback = callback
		self.icon2Location = icon2Location
		self.icon3Location = icon3Location
		self.initialString = ""
		self.tempString = ""
		self.tempNotification= UpdateNotification()
		self.temp= TBIconMaker(update_click, self.tempNotification,  icon2Location, icon3Location, self)
		self.Bind(wx.EVT_TIMER, self.timeStamp)
		self.timeStamp(self.interval)
	#
	def updating(self):
		try:
			subprocess.call(["Terminal", "--disable-server", "-e", "sudo pulley update"])
		except Exception:
			pass
		#
		self.callback(self, self.temp, self.tempNotification)
	#
	def timeStamp(self, unknown):
		try:
			self.tempString = subprocess.Popen(["nmcli", "-f", "TIMESTAMP-REAL", "con"], stdout=subprocess.PIPE)
		except Exception:
			pass
		#
		if self.initialString != self.tempString:
			self.callback(self, self.temp, self.tempNotification)
		#
		self.initialString = self.tempString
    #
	def timer(self):
		self.Start(self.interval * 1000, wx.TIMER_ONE_SHOT)
	#
#

def main(interval, icon2Location, icon3Location):	
	app= wx.App()
	UpdateChecker(int(interval), check_updates, icon2Location, icon3Location)
	app.MainLoop()
#

if __name__ == '__main__':
	if len(sys.argv) > 4:
		print "Initial User Failure"
		print >> sys.stderr, "Usage: ", sys.argv[0], "<interval> <path to icon 2> <path to icon 3>"
		sys.exit(2)
	#

	main(sys.argv[1], sys.argv[2], sys.argv[3])
#
